﻿/*-------------------------------------------------------------------------
* 命名空间: SiliconSelect.PlcComunication.Model/PlcStateModel
* 类       名: PlcStateModel
* 功      能:  TD
* 时      间:  2023/7/27 13:53:47
* 版      本:  V1.0
* 作      者:  Fioman
* 格      言:  Talk is cheap,show me the code ^_^
*-------------------------------------------------------------------------*/
using SiliconSelect.Base;
using SiliconSelect.Common;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Controls;
using System.Windows.Media;

/*
 * 目前的数据类型对应是:
 * Plc心跳  UINT -> ushort  D1     3s内变化 0-1 或者 1-0   pc心跳  UINT D0 3s内变化 0-1 或者 1-0
 * 设备状态  Uint-> ushort  D3   0: 自动运行 1: 待机 2: 正常停机 3: 故障停机 4: 待料 5: 满料  
 * PC状态  Uint->ushort D2   1: 运行  2: 停止 3: 出错
 * 已经停机时间: Uint -> ushort D4
 * 
 * 测试电阻工位  
 * 触发测试 Uint D100       测试反馈 UINT-> ushort  D101
 * 电阻率对应流水号  UINT D120   
 *                       
 * 分选:
 * 触发分选 Uint D110
 * 分选地址 Uint D111
 * 分选流水号 Uint D121
 */
namespace SiliconSelect.PlcComunication.Model
{
    public class PlcStateModel : NotifyBase
    {
        public Dictionary<ushort, string> PlcRunStatusDescription = new Dictionary<ushort, string>()
        {
            {0,"自动运行" },
            {1,"待机" },
            {2,"正常运行" },
            {3,"故障停机" },
            {4,"待料" },
            {5,"满料" }
        };

        /// <summary>
        /// 心跳超时时间,超过这个时间就认为PLC心跳掉线
        /// </summary>
        public static double HeartOnlineMax = 3.0;

        /// <summary>
        /// PLC是否在线
        /// </summary>
        private string? _isOnline;

        public string? IsOnline
        {
            get { return _isOnline; }
            set
            {
                if (value == "已连接")
                {
                    IsOnlineColor = new SolidColorBrush(Colors.Green);
                }
                else
                {
                    IsOnlineColor = new SolidColorBrush(Colors.Red);
                }
                SetProperty(ref _isOnline, value);
            }
        }

        private SolidColorBrush? _isOnlineColor;

        public SolidColorBrush? IsOnlineColor
        {
            get { return _isOnlineColor; }
            set { SetProperty(ref _isOnlineColor, value); }
        }
        /// <summary>
        /// PLC的Ip地址
        /// </summary>
        public string? Ip { get; set; }

        /// <summary>
        /// PLC的端口号
        /// </summary>
        public int Port { get; set; }

        /// <summary>
        /// 设备心态是否在线
        /// </summary>
        public bool HeartIsAlive = false;

        /// <summary>
        /// PLC的运行状态
        /// </summary>
        private string? _plcRunStatus = "未连接";

        public string? PlcRunStatus
        {
            get { return _plcRunStatus; }
            set
            {
                switch (value)
                {
                    case "自动运行":
                        RunStatusColor = new SolidColorBrush(Colors.Green);
                        break;
                    case "待机":
                        RunStatusColor = new SolidColorBrush(Colors.Gray);
                        break;
                    case "正常运行":
                        RunStatusColor = new SolidColorBrush(Colors.Green);
                        break;
                    case "故障停机":
                        RunStatusColor = new SolidColorBrush(Colors.Red);
                        break;
                    case "待料":
                        RunStatusColor = new SolidColorBrush(Colors.Gray);
                        break;
                    case "满料":
                        RunStatusColor = new SolidColorBrush(Colors.Red);
                        break;
                    default:
                        value = "未连接";
                        RunStatusColor = new SolidColorBrush(Colors.Red);
                        break;
                }
                SetProperty(ref _plcRunStatus, value);
            }
        }

        private SolidColorBrush? _runStatusColor = new SolidColorBrush(Colors.Gray);

        public SolidColorBrush? RunStatusColor
        {
            get { return _runStatusColor; }
            set { SetProperty(ref _runStatusColor, value); }
        }


        /// <summary>
        /// 更新上一次读取的值相同的时间.当值变化的时候,这个值就更新.
        /// </summary>
        private DateTime? _lastChangeTime = null;

        public DateTime? LastChangeTime
        {
            get { return _lastChangeTime; }
            set { SetProperty(ref _lastChangeTime, value); }
        }

        /// <summary>
        /// 最后一次读取的心跳的值
        /// </summary>
        private ushort _lastReadHeartVal;

        public ushort LastReadHeartVal
        {
            get { return _lastReadHeartVal; }
            set
            {
                if (value != _lastReadHeartVal || LastChangeTime == null)
                {
                    LastChangeTime = DateTime.Now;
                }
                else
                {
                    TimeSpan timeSpan = (TimeSpan)(DateTime.Now - LastChangeTime)!;
                    if (timeSpan.TotalSeconds > HeartOnlineMax)
                    {
                        // 设备心跳不在线,检测到设备掉线
                        if (HeartIsAlive)
                        {
                            HeartIsAlive = false;
                            LogHelper.WriteLog(LogType.Fatal, $"检测到设备心跳掉线,改变设备状态为掉线");
                            IsOnline = "已断开";
                        }
                    }
                }
                SetProperty(ref _lastReadHeartVal, value);
            }
        }

        /// <summary>
        /// 最后一次写入PLC的时间,心跳时间
        /// </summary>
        private DateTime? _lastWriteTime;

        public DateTime? LastWriteTime
        {
            get { return _lastWriteTime; }
            set { SetProperty(ref _lastWriteTime, value); }
        }


        /// <summary>
        /// 最后一次写入的心跳的值
        /// </summary>
        private ushort _lastWriteHeartVal;

        public ushort LastWriteHeartVal
        {
            get { return _lastWriteHeartVal; }
            set
            {
                SetProperty(ref _lastWriteHeartVal, value);
                LastWriteTime = DateTime.Now;
            }
        }

        /// <summary>
        /// _plc停机时间,转换为小时,如果它的时间单位是ms,就转换为小时
        /// </summary>
        private string? _plcStopTime = "0";

        public string? PlcStopTime
        {
            get { return _plcStopTime; }
            set
            {
                double hours = double.Parse(value!) / (1000.0 * 60 * 60);
                value = hours.ToString() + " h";
                SetProperty(ref _plcStopTime, value);
            }
        }

    }
}
